/*
 * @description 购买节点 相关函数
 * @fileName buynodes.js
 * @date 2025/07/25 18:22:38
 */

const Apis = {
  // 指定会员的推广权限
  index: '/app/admin/v1-api/getUserExtend?type=2',

  // 城市列表
  citys: '/app/admin/v1-api/getAreaList',
  // ISP列表
  ispOptions: '/app/admin/v1-api/getIspList',
  // IP段列表
  ipOptions: '/app/admin/v1-api/getIpSegmentList',
  // 可开地区列表
  openOptions: '/app/admin/v1-api/getOpenList',

  // 地区列表
  areaList: '/app/admin/v1-api/getRegionList',
  // /app/admin/v1-api/getRegionList?line_id=1&area_id=&operator_id=&ip_segment=&open=

  // 自定义账号列表
  customAcountList: '/app/admin/v1-api/getCustomTypeList',

  // 自选端口
  choosePorts: '/app/admin/v1-api/getCustomPortList',

  // 保存订单
  saveFormData: '/app/admin/v1-api/createOrder',
}

/**
 * RenderSelectElement
 * @param {*} options
 * @param {*} callback
 */
const renderSelectElement = (
  options = {
    el,
    name,
    initValue: '',
    filterable: false,
    data: [],
  },
  callback
) => {
  layui.xmSelect.render({
    ...options,
    // el: '#line_id',
    // name: 'line_id',
    model: { icon: 'hidden', label: { type: 'text' } },
    clickClose: true,
    radio: true,
    // layVerify: 'required',
    on: function (data) {
      callback && callback(data.arr) // 只返回更新后的数据 `data.arr`
    },
  })
}

// 执行切换 页面状态
const excuteSwitch = () => {
  const $ = layui.$
  let key = 'layui-show'
  const $items = $('#switch-window-tab.layui-tab-content > .layui-tab-item')
  $.each($items, function () {
    let _ = $(this)
    if (_.hasClass(key)) _.removeClass(key)
    else _.addClass(key)
    // NOTE:  Step2 add gaps
    $('#gaps')[$items.eq(0).hasClass(key) ? 'hide' : 'show']()
  })
}

function CommonApis() {
  const $ = layui.$
  return {
    // 首页 get index apis
    getIndexInfo: function (callback) {
      $.ajax({
        url: Apis.index,
        type: 'GET',
        data: {},
        success: function (res) {
          layer.closeAll('loading')
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          callback && callback(res.data || {})
        },
      })
    },
    // 省份列表
    getCitys: function (callback) {
      $.ajax({
        url: Apis.citys,
        type: 'GET',
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // ISP列表
    getIsp: function (callback) {

      let params = new URL(location.href).searchParams
      let line_id = params.get('line_id');

      $.ajax({
        url: Apis.ispOptions,
        type: 'GET',
        data: {line_id:line_id},
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // IP段列表
    getIp: function (callback) {
      $.ajax({
        url: Apis.ipOptions,
        type: 'GET',
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // 可开地区列表
    getOpen: function (callback) {
      $.ajax({
        url: Apis.openOptions,
        type: 'GET',
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // 地区列表
    // /app/admin/v1-api/getRegionList?line_id=1&area_id=&operator_id=&ip_segment=&open=
    // line_id 线路ID
    // area_id 省份ID
    // operator_id 运行商ID
    // ip_segment ip段
    // open 可开地区
    // 地区选项列表
    getServices: function (formData, callback) {
      $.ajax({
        url: Apis.areaList,
        type: 'POST',
        data: {
          ...formData,
        },
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // 自定义账号列表
    getCustomAcountOps: function (callback) {
      $.ajax({
        url: Apis.customAcountList,
        type: 'GET',
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // 自选端口
    getChoosePorts: function (callback) {
      $.ajax({
        url: Apis.choosePorts,
        type: 'GET',
        success: function (res) {
          if (res.code) {
            layui.layer.msg(res.msg)
            return
          }
          const list = res.data || []
          callback && callback(list)
        },
      })
    },

    // 保存订单
    saveForm: function (formData, callback) {
      // [Save Order]
      // line_id=
      // game_id=
      // ip_segment=
      // duration=
      // custom_type=
      // account=
      // pass=
      // port=
      // data=[{"rid":1,"number":1},{"rid":2,"number":1}]
      $.ajax({
        url: Apis.saveFormData,
        type: 'POST',
        data: {
          ...formData,
        },
        success: function (res) {
          if (res.code) {
            layer.closeAll('loading')
            layui.layer.msg(res.msg)
            return
          }
          callback && callback(res || [])
        },
      })
    },
  }
}

function CommonRenders() {
  const $ = layui.$
  return {
    /**
     * @description 渲染游戏 Tabs Show Elements.
     * @returns [ TabInstances ] return tab instances.
     */
    renderStepOneTab: function () {
      const tab = layui.tab

      // 65-90 ascii code A-Z
      let MW = []
      for (let i = 65; i <= 90; i++) {
        MW.push(String.fromCharCode(i))
      }

      let MWList = MW.map((value, index, array) => ({
        id: `${index + 1}`,
        title: value,
        url: '/app/admin/v1-node/buynodes_games?letter=' + value,
        close: false,
      }))

      const tabInstance = tab.render({
        elem: 'tab-gamebox',
        roll: false,
        tool: false,
        width: '100%',
        height: '485px', // temporary.
        index: 0,
        session: true,
        tabMax: 26,
        data: JSON.parse(JSON.stringify(MWList)), // 防止对象引用问题,
        preload: false,
        closeEvent: function (id) {
          layer.msg('关闭回调')
        },
      })

      // Remove MouseRightEvent.
      $(
        "body .layui-tab[lay-filter='" +
          tabInstance.option.elem +
          "'] .layui-tab-title"
      ).off('contextmenu')

      // tabInstance click event.
      tabInstance.click((id) => {
        var $iframe = $(
          ".layui-tab[lay-filter='" +
            tabInstance.option.elem +
            "'] .layui-tab-content"
        ).find("iframe[id='" + id + "']")

        var iframeUrl = $iframe.attr('src')

        if (!iframeUrl || iframeUrl === 'about:blank') {
          MWList.forEach(function (item, index) {
            if (item.id === id) iframeUrl = item.url
          })
          $iframe.attr('src', iframeUrl)
        }
      })

      return tabInstance
    },

    // 渲染城市列表
    renderCitys: function (list = []) {
      const $parent = $('.gameinfo_citys')
      if (!list.length) {
        $parent.html(
          '<i style="color: #999; user-select: none">暂无相关城市</i>'
        )
        return
      }

      const fragement = new DocumentFragment()
      // .pear-btn-primary
      const setButton = (name, id = 'all') =>
        $(
          `<button type="button" plain class="pear-btn pear-btn-xs " data-id="${id}">${name}</button>`
        )[0]
      fragement.appendChild(setButton('全部', 'all'))
      $.each(list, function (index, item) {
        fragement.appendChild(setButton(item.name, item.id))
      })

      $parent.html(fragement)
    },

    // 渲染下拉框(ips, 运营商, 开放区域)
    renderSelect: function (options, callback) {
      renderSelectElement(options, callback)
    },

    // 渲染服务商列表
    renderServices: function (list = []) {
      const fragement = new DocumentFragment()
      $.each(list, function (index, item) {
        const needDisabled = item.surplus_number <= 0 // 暂无可售出服务IP.

        // <div class="new">
        //   <img src="/app/admin/admin/images/new.png" alt="" />
        // </div>
        fragement.append(
          $(`<li
              class="service"
              data-id="${item.id}"
              data-type="${item.type}"
              data-line-id="${item.line_id}"
              data-area-id="${item.area_id}"
              data-type-id="${item.type_id}"
              data-sale="${needDisabled ? 0 : 1}"
              style="padding: 6px 10px;"
            >
              <div class="flex align-center justify-between">
                <span class="nodes-name" title="${item.name}">${item.name}</span>
                <input
                  name="service_${item.area_id}_${item.id}"
                  class="layui-input layui-input-sm"
                  type="number"
                  min="0"
                  value="${item.number || 0}"
                  max="${item.surplus_number}"
                  placeholder="数量"
                  style="max-width: 80px; display: ${
                    needDisabled ? 'none' : 'block'
                  }"
                />
              </div>
              <div class="middleinfos" style="margin-bottom: 0">
                <span>${item.area_name}</span>
                <span>
                  <i class="layui-icon layui-icon-wifi"></i>
                  ISP:
                  <i class="text-color-blue signal-from">${
                    item.operator_name
                  }</i>
                </span>
              </div>
              <div class="flex justify-between btns">
                <!-- 总量&可售 .layui-btn-danger -->
                <button class="pear-btn pear-btn-primary pear-btn-xs pear-btn-${
                  needDisabled ? 'disabled' : ''
                }">
                  总量:${item.ip_number}
                </button>
                <button class="pear-btn pear-btn-primary pear-btn-xs pear-btn-${
                  needDisabled ? 'disabled' : ''
                }" >
                  可售:${item.surplus_number}
                </button>
              </div>
            </li>`)[0]
        )
      })
      if (!list.length) {
        fragement.append(
          $(`<i style="color: #999; user-select: none">暂无可售出服务</i>`)[0]
        )
      }
      $('.nodes-wrapper').html(fragement)
    },
    reRenderService: function (removeClass = false) {
      const $lis = $('.nodes-wrapper li')
      $.each($lis, function (index, liElement) {
        const val = Number($(liElement).find('input[type="number"]').val())
        if (val && !removeClass) {
          $(liElement).addClass('flag')
        } else {
          $(liElement).removeClass('flag')
        }
      })
    },

    // 渲染时长
    renderBNTimes: function (list) {
      if (!list.length) return
      const fragement = new DocumentFragment()
      const setButton = (info, className = '') =>
        $(
          `<button type="button" plain class="pear-btn pear-btn-sm ${className}" data-score="${info.score}" data-type="${info.type}">${info.name}</button>`
        )[0]

      $.each(list, function (index, item) {
        if (item.show)
          if (item.type === 'btn')
            fragement.append(
              setButton(
                {
                  ...item,
                },
                'pear-btn-disabled'
              )
            )
          else
            fragement.append(
              setButton(
                {
                  ...item,
                },
                item.default ? 'pear-btn-primary' : ''
              )
            )
      })

      $('.bn-times').html(fragement)
    },

    // 渲染自定义账号
    renderAccountsOps: function (list) {
      if (!list.length) return
      const fragement = new DocumentFragment()
      $.each(list, function (index, item) {
        fragement.append(
          $(
            `<input
              type="radio"
              name="custom_type"
              data-id="${item.id}"
              data-pid="${item.pid}"
              value="${item.value}"
              title="${item.name}"
              ${index === 1 ? 'checked' : ''}
              lay-filter="account"
            />`
          )[0]
        )
      })
      $('#custom-accounts').html(fragement)
      layui.form.render() // Rebuild.
    },
  }
}

/**
 * 创建游戏详情Class类、执行流程
 * 函数与原型链的方式创建 or 工厂函数
 */
function GameDetail() {
  const params = new URL(location.href).searchParams
  const LINE_ID = params.get('line_id')

  const $ = layui.$
  const commonApis = CommonApis()
  const commonRenders = CommonRenders()

  return {
    userExtend: null, // 存放用户区域推广权限 Object.
    // 查询筛选条件
    filterObject: {
      line_id: LINE_ID,
      area_id: '',
      operator_id: '',
      ip_segment: '',
      open: '',
      game_id: '',
    },
    // 提交展示内容
    selData: {
      area: 0, // 已选择地区 Length
      ip: 0, // 已选择Ips Length
      score: 0, // 消耗金币
    },
    nodes: [], // 当前所有节点
    selnodes: null, // 选中的节点
    // add node to selnodes
    setSelNode: function (item) {
      // additional key number: count
      const temp = this.selnodes || {} // default object
      const { id } = item

      let num = Number(item.number)
      if (isNaN(num)) num = 1

      if (Object.getOwnPropertyNames(temp).includes(`${id}`)) {
        temp[id].number = num
      } else temp[id] = Object.assign({}, item)

      this.selnodes = Object.assign({}, temp)
    },
    removeSelNode: function (id) {
      const temp = this.selnodes || {} // default object
      if (Object.getOwnPropertyNames(temp).includes(`${id}`)) {
        delete temp[id]
      }
    },
    formData: null,
    setFormData: function (data) {
      let formData = this.formData || {}
      if (!formData) formData = {}
      Object.assign(formData, data)
      this.formData = formData
    },
    // 存放用户当前服务器权限
    setIndexInfo: function (infos) {
      if (!infos) return

      // this.userExtend = infos.user_extend
      const item = infos.user_extend.find((item) => item.line_id == LINE_ID)

      if (item) {
        this.userExtend = item
        const list = formatTiemsArrs(item)
        // Render Area.
        commonRenders.renderBNTimes(list)
      }
    },
    initialization: function (gameinfo) {
      // const { from, medhod } = gameinfo
      // const { id, letter, name } = gameinfo.data
      const that = this

      $('.gameinfo_title strong').text(gameinfo.data.name)
      that.filterObject.game_id = gameinfo.data.id

      layer.load()
      // useless.
      // commonApis.getIp((list) => {
      //   commonRenders.renderSelect(
      //     {
      //       el: '#ip_segment',
      //       name: 'ip_segment',
      //       data: list,
      //     },
      //     (data) => {
      //       const item = (data && data[0]) || {}
      //       that.filterObject.ip_segment = item.value ?? ''
      //       that.searchAreaService(true)
      //     }
      //   )
      // })
      commonApis.getIsp((list) => {
        list.unshift({ name: '全部', value: '' }) // NOTES: 增加全部的选项
        $('#operator_id_btns').html('')
        const fragement = new DocumentFragment()
        $.each(list, function (index, item) {
          fragement.append(
            $(`<button type="button" round class="pear-btn pear-btn-xs ${index == 0 ? 'pear-btn-primary' : ''}" data-id="${item.id}">${item.name}</button>`)[0]
          )
        })
        $('#operator_id_btns').html(fragement)
        $('#operator_id_btns button').on('click', function () {
          const $btn = $($(this).context)
          let id = $btn.data('id')
          if (that.filterObject.operator_id == id) return
          if (id === "undefined") id = ''
          $btn.siblings().removeClass('pear-btn-primary')
          $btn.addClass('pear-btn-primary')
          that.filterObject.operator_id = id
          that.searchAreaService(true)
        })

        // commonRenders.renderSelect(
        //   {
        //     el: '#operator_id',
        //     name: 'operator_id',
        //     data: list.map(({ name, id }) => ({
        //       name,
        //       value: id,
        //     })),
        //   },
        //   (data) => {
        //     const item = (data && data[0]) || {}
        //     that.filterObject.operator_id = item.value ?? ''
        //     that.searchAreaService(true)
        //   }
        // )
      })
      commonApis.getOpen((list) => {
        commonRenders.renderSelect(
          {
            el: '#open',
            name: 'open',
            data: list,
          },
          (data) => {
            const item = (data && data[0]) || {}
            that.filterObject.open = item.value ?? ''
            that.searchAreaService(true)
          }
        )
      })
      commonApis.getCitys(commonRenders.renderCitys)
      this.searchAreaService()
      commonApis.getCustomAcountOps(commonRenders.renderAccountsOps)

      // 渲染端口 - 模拟
      commonRenders.renderSelect({
        el: '#port',
        name: 'port',
        initValue: [{ id: 1, name: '系统默认', value: '0' }],
        data: [{ id: 1, name: '系统默认', value: '0' }],
      })
      // commonApis.getChoosePorts(
      //   (list) => {
      //     commonRenders.renderSelect({
      //       el: '#port',
      //       name: 'port',
      //       data: list,
      //     })
      //   },
      //   (data) => {}
      // )
      layer.closeAll('loading')
    },

    // 搜索区域服务数据
    searchAreaService: function (isShowLoading = false) {
      const that = this
      isShowLoading && excuteLoad()

      const getNum = (id) => {
        const temp = that.selnodes || {} // default object
        if (Object.getOwnPropertyNames(temp).includes(`${id}`)) {
          return temp[id].number
        }
        return 0
      }

      commonApis.getServices(Object.assign({}, that.filterObject), (list) => {
        list = list.map((item) => ({
          ...item,
          number: getNum(item.id),
        }))
        that.nodes = list
        commonRenders.renderServices(list)
        isShowLoading && excuteLoad(true)
      })
    },
    fetchService: function () {
      this.searchAreaService(true)
    },

    // 清空选择
    cleanSelect: function () {
      const $lis = $('.nodes-wrapper li')
      $.each($lis, function (index, liElement) {
        const sale = $(liElement).attr('data-sale')
        if (sale == 1) {
          $(liElement).find('input[type="number"]').val('')
        }
      })
      this.selnodes = null
    },

    // 自动选择服务器
    autoSelect: function () {
      const that = this
      that.cleanSelect()

      const autoCount = Number($('input.number-input-value').val() || 0) // 自动选择数量
      if (isNaN(autoCount)) {
        $('input.number-input-value').val('')
        layui.layer.msg('请输入正确的数量')
        return
      }

      const $lis = $('.nodes-wrapper li')
      const nodeLen = that.nodes.length

      // 可售出总ip数
      let initialVal = 0 // 可被选择的总 ip 数量
      const total = that.nodes.reduce(
        (pre, cur) => (pre += Number(cur.surplus_number)),
        initialVal
      )

      // 无可售出节点计算
      // 节点中无可售出数量
      const initialNLVal = 0
      const nLifeNodes = that.nodes.reduce(
        (pre, cur) => (pre += Number(cur.surplus_number <= 0 ? 1 : 0)),
        initialNLVal
      )

      if (autoCount > total) {
        return layui.layer.msg('自动选择数量错误,不可超过总量')
      }

      let lifeNodeCount = nodeLen - nLifeNodes // 剩余有可出售节点

      if (lifeNodeCount < autoCount) {
        /**
         * @deprecated 剩余节点 少于自动选择数量 执行此处
         * while autoCount
         * for 便利顺序判断是否存在可售出 += 1
         *  不存在继续便利 break
         * while again.
         */
        let s = autoCount
        while (s > 0) {
          const l = function (t) {
            if (s <= 0) return 0
            if (
              that.nodes[t].surplus_number <=
              Number($($lis.get(t)).find('input[type="number"]').val() || 0)
            )
              return 1
            else {
              s -= 1
              let num = Number(
                $($lis.get(t)).find('input[type="number"]').val() || 0
              )

              num += 1

              $($lis.get(t)).find('input[type="number"]').val(num)

              that.setSelNode({
                ...that.nodes[t],
                number: num,
              })
            }
          }

          for (var o, r = 0; r < nodeLen; r++) {
            o = l(r)
            if (0 === o) break
          }
        }
      } else {
        /**
         * @deprecated 自动输入少于剩余节点 执行此处
         * 随机 index
         * 判断是否符合、不复合 do-while 去挑选符合 index； (此处增加条件 new-index 不能存在 随机 index 中存在重新筛选)
         * nodes[index] = 1 填充数据
         */

        let c = [],
          d = new Set()

        if (autoCount > 0) {
          while (d.size < autoCount) {
            var p = Math.floor(Math.random() * nodeLen)
            d.add(p)
          }
          c = Array.from(d)
        }

        for (var h = 0; h < c.length; h++) {
          const liEle = $($lis.get(c[h]))[0]
          if (
            that.nodes[c[h]].surplus_number <=
            ($(liEle).find('input[type="number"]').val() || 0)
          ) {
            let m = 0
            do {
              m = Math.floor(Math.random() * nodeLen)
            } while (
              c.includes(m) ||
              that.nodes[m].surplus_number <=
                ($($lis.get(m)[0]).find('input[type="number"]').val() || 0)
            )
            c[h] = m
          }

          $($($lis.get(c[h]))[0])
            .find('input[type="number"]')
            .val(1)

          that.setSelNode({
            ...that.nodes[c[h]],
            number: 1,
          })
        }
      }
    },

    // 订单确认
    confirmOrder: function () {
      const that = this
      const data = []

      const lis = $('.nodes-wrapper li')
      $.each(lis, function (index, liElement) {
        const val = Number($(liElement).find('input[type="number"]').val())
        if (val) {
          data.push({
            name: $(liElement).find('.nodes-name').text(),
            count: val,
            score: that.selData.score * val,
          })
        }
      })

      layer.open({
        type: 1,
        title: '订单确认',
        content: $('.order-confirm-wrapper'),
        btnAlign: 'r',
        btn: ['确认', '取消'],
        // area: ['600px', '500px'],
        area: isMobile() ? ['100%', '100%'] : ['60%', '95%'],
        yes: function (index, layero) {
          that.orderDetail()
        },
        btn2: function (index, layero) {
          layer.close(index)
        },
        success: function () {
          layui.table.render({
            elem: '#confirm-order-table',
            height: 'full',
            data,
            skin: 'line',
            toolbar: false,
            cols: [
              [
                { field: 'name', title: '节点' },
                { field: 'count', title: '数量' },
                { field: 'score', title: '金币' },
              ],
            ],
          })
        },
      })
    },

    /**
     * 格式化表单数据
     */
    formatFormData() {
      const that = this
      // line_id=
      // game_id=
      // ip_segment=
      // duration=
      // custom_type=
      // account=
      // pass=
      // port=
      // data=[{"rid":1,"number":1},{"rid":2,"number":1}]

      // 增加两个字段
      // remark 备注
      // group_name 分组填写

      const formdata = layui.form.val('fixed-form')
      const $btnDuration = $('.bn-times button.pear-btn.pear-btn-primary')
      const data = []
      for (const [region_id, item] of Object.entries(that.selnodes)) {
        data.push({
          region_id,
          number: item.number,
        })
      }

      return {
        remark: formdata.remark || '',
        group_name: formdata.group_name || '',
        line_id: LINE_ID,
        game_id: that.filterObject.game_id,
        // ip_segment: that.filterObject.ip_segment,
        duration: $btnDuration.attr('data-type'),
        custom_type: formdata.custom_type,
        account: $('#account').val(),
        pass: $('#pass').val(),
        port: '0',
        data: JSON.stringify(data),
      }
    },

    // 订单详情
    orderDetail: function () {
      const that = this
      const formData = that.formatFormData()

      layer.load()
      // const data = [
      //   {
      //     user_id: 2,
      //     user_name: 'kaifa',
      //     line_id: '1',
      //     game_id: '7',
      //     duration: 'test6h',
      //     amount: 0,
      //     expire_time: '2025-08-03 05:16:00',
      //     remark: '',
      //     region_id: 1,
      //     code: 'ysgz19',
      //     ip: '182.43.73.41',
      //     port: '51001',
      //     ip_ems: '192.168.0.13',
      //     account: 'x2XLClAY',
      //     pass: 'x2XLClAY',
      //     created_at: '2025-08-02 23:16:00',
      //   },
      //   {
      //     user_id: 2,
      //     user_name: 'kaifa',
      //     line_id: '1',
      //     game_id: '7',
      //     duration: 'test6h',
      //     amount: 0,
      //     expire_time: '2025-08-03 05:16:00',
      //     remark: '',
      //     region_id: 1,
      //     code: 'ysgz19',
      //     ip: '182.43.73.41',
      //     port: '51001',
      //     ip_ems: '192.168.0.13',
      //     account: 'x2XLClAY',
      //     pass: 'x2XLClAY',
      //     created_at: '2025-08-02 23:16:00',
      //   },
      // ]
      commonApis.saveForm(formData, (res) => {
        const data = res.data;
        const dataStr = data
          .map(
            (item) =>
              `${item.ip}|${item.port}|${item.account}|${item.pass}|${item.expire_time}`
          )
          .join('\n')

        const closedExecute = () => {
          // clean form data.
          that.selnodes = null
          $('input[name="account"]').val('')
          $('input[name="pass"]').val('')
          $('input[name="group_name"]').val()
          $('input[name="remark"]').val()

          $('#autoinput-cancel').click()
          that.searchAreaService(true)
        }

        layer.closeAll()
        layer.alert(res.msg)
        setTimeout(() => {
          layer.open({
            type: 1,
            title: '订单数据',
            content: $('.order-confirm-wrapper'),
            btnAlign: 'r',
            btn: ['文本导出', '一键复制', '关闭'],
            area: isMobile() ? ['100%', '100%'] : ['60%', '95%'],
            yes: function (index, layero) {
              // 设置文本导出
              downloadTextAsFile(dataStr, '订单数据.txt')
            },
            btn2: function (index, layero) {
              copyText(dataStr)
            },
            btn3: function (index, layero) {
              // clean form data.
              closedExecute()
              layer.close(index)
            },
            cancel: function (index, layero) {
              closedExecute()
              layer.close(index)
            },
            success: function () {
              layui.table.render({
                elem: '#confirm-order-table',
                height: 'full',
                data,
                skin: 'line',
                toolbar: false,
                cols: [
                  [
                    { field: 'ip', title: 'IP' },
                    { field: 'port', title: '端口', width: 90 },
                    { field: 'account', title: '用户名' },
                    { field: 'pass', title: '密码' },
                    { field: 'expire_time', title: '到期时间' },
                  ],
                ],
              })
            },
          })
        }, 500)
        // callback end.
      })
    },
  }
}

/**
 * 格式化区域服务数据 - 格式化成数组时长信息
 * @param {object} infos 当前区域的详细信息
 * @returns {array}
 */
function formatTiemsArrs(infos) {
  const { zp_show = 0, yp1_show = 0, rp_show = 0 } = infos
  const tipsArs = [
    yp1_show ? `月卡${parseFloat(infos.yp1)}金币` : undefined,
    zp_show ? `周卡${parseFloat(infos.zp)}金币` : undefined,
    rp_show ? `天卡${parseFloat(infos.rp)}金币` : undefined,
  ].filter(key => key)

  return [
    {
      name: '1天',
      score: infos.rp,
      type: 'rp',
      show: infos.rp_show == '1' && infos.rp_switch,
    },
    {
      name: '7天',
      score: infos.zp,
      type: 'zp',
      show: infos.zp_show == '1' && infos.zp_switch,
    },
    {
      name: '1个月',
      score: infos.yp1,
      type: 'yp1',
      show: infos.yp1_show == '1' && infos.yp1_switch,
      default: true,
    },
    {
      name: '3个月',
      score: infos.yp3,
      type: 'yp3',
      show: infos.yp3_show == '1' && infos.yp3_switch,
    },
    {
      name: '6个月',
      score: infos.yp6,
      type: 'yp6',
      show: infos.yp6_show == '1' && infos.yp6_switch,
    },
    {
      name: '1年',
      score: infos.np,
      type: 'np',
      show: infos.np_show == '1' && infos.np_switch,
    },
  ]
    .concat(
      infos.test_switch == '1'
        ? [
            {
              name: '测试卡2小时',
              score: 0,
              type: 'test2h',
              show: infos.test2h_switch == '1',
            },
            {
              name: '测试卡6小时',
              score: 0,
              type: 'test6h',
              show: infos.test6h_switch == '1',
            },
            {
              name: '测试卡12小时',
              score: 0,
              type: 'test12h',
              show: infos.test12h_switch == '1',
            },
          ]
        : []
    )
    .concat([
      {
        type: 'btn',
        name: tipsArs.join('/'),
        show: Boolean(tipsArs.length),
      },
    ])
}

/**
 * 执行加载动画
 * @param {boolean} isEnd 是否结束
 */
function excuteLoad(isEnd = false) {
  if (isEnd) {
    layer.closeAll('loading')
  } else {
    layer.load(1, {
      shade: [0.6, '#000'],
    })
  }
}

/**
 * @description 清除城市选中状态
 */
function cleanCitysStatus(callback) {
  const $ = layui.$
  const $btns = $('.gameinfo_citys button')
  layui.$.each($btns, (index, btn) => $(btn).removeClass('pear-btn-primary'))
  callback && callback()
}

// 获取选中的服务
function formatCountValidLi(selnodes) {
  const $ = layui.$
  const that = this

  if (!selnodes) return { area: 0, ip: 0, num: 0 }

  const list = Object.entries(selnodes)

  const areaN = new Set()
  const ipN = list.length
  let num = 0 // 数量

  for (const [id, item] of list) {
    areaN.add(item.area_id)
    num += item.number || 1
    // ipN.add(id)
  }

  return {
    area: areaN.size,
    ip: ipN,
    num,
  }
}

/**
 * @description 检查并计算选中的服务数量(地区、IP、金币)
 */
function checkCountToSel(objs) {
  const $ = layui.$
  const { area = 0, ip = 0, score = 0 } = objs
  $('#sel-area-count').text(area)
  $('#sel-ip-count').text(ip)
  $('#sel-score-count').text(parseFloat(score))
}

// 更新显示
function updateShowTips($btn, selnodes) {
  const $ = layui.$
  if (!$btn)
    $btn = $('.bn-times button.pear-btn-primary:not([data-type="btn"])')

  let score = $btn.attr('data-score')

  const ds = formatCountValidLi(selnodes)

  gameDetail.selData = Object.assign(gameDetail.selData, ds, {
    score,
  })

  let money = Number(ds.num * score)
  money = isNaN(money) ? 0 : money

  layui.layer.msg(`已选 ${ds.area} 个地区, ${ds.num} 个IP,  ${money} 金币`)
  checkCountToSel(
    Object.assign(ds, {
      score: ds.num * score,
      ip: ds.num, // ip总数量、不是ip服务器
    })
  )
}
